package com.youth.custom.tag;

import java.io.IOException;
import java.util.ArrayList;
import java.util.Enumeration;
import java.util.List;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.jsp.JspException;
import javax.servlet.jsp.JspWriter;
import javax.servlet.jsp.tagext.TagSupport;

import org.apache.commons.lang3.StringUtils;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;

/**
 * 前端分页Tag.
 */
public class PaginationTag extends TagSupport {
	private static final long serialVersionUID = -1104820782784107929L;
	private static Log log = LogFactory.getLog(PaginationTag.class);

	// private PageInfo pageInfo; // 分页信息(必须)
	private Integer currentPage;// 当前页
	private String divClass;// 最外层div样式
	private String requestUrl; // 请求地址(对于GET方式可选)
	private Integer pageSize;
	private Integer totalCount;

	@Override
	public int doStartTag() throws JspException {
		PageInfo pageInfo = new PageInfo();
		pageInfo.setCurrentPage(currentPage);
		if (null != pageSize && 0 != pageSize) {
			pageInfo.setPageSize(pageSize);
		}
		pageInfo.setTotalCount(totalCount);
		JspWriter out = this.pageContext.getOut();
		if (pageInfo.getPageSize() > totalCount) {
			// 总量大于页面大小则不显示分页
		} else {
			StringBuffer sb = new StringBuffer();
			generatePager(sb, pageInfo);
			try {
				out.print(sb.toString());
			} catch (IOException e) {
				log.error("Fail to generate & write pagination.", e);
			}
		}

		return SKIP_BODY;
	}

	private void generatePager(StringBuffer sb, PageInfo pageInfo) {
		HttpServletRequest req = (HttpServletRequest) pageContext.getRequest();
		String uri = null;
		if (StringUtils.isEmpty(requestUrl)) {
			Object attrUri = req.getAttribute("javax.servlet.forward.request_uri");
			if (attrUri != null && (attrUri instanceof String)) {
				uri = (String) attrUri;
			}
			if (uri == null) {
				uri = req.getRequestURI();
			}
		}

		String condition = getCondition(req);
		if (StringUtils.isNotBlank(divClass)) {
			sb.append("<div class=\"" + divClass + "\">");
		} else {
			sb.append("<div class=\"pager\">");
		}

		sb.append("<ul>");
		if (currentPage > 1) {
			if (StringUtils.isNoneBlank(condition)) {
				sb.append("<a href=\"" + uri + "?" + condition + "&currentPage=" + (currentPage - 1));
			} else {
				sb.append("<a href=\"" + uri + "?currentPage=" + (currentPage - 1));
			}
			if (null != pageSize && 0 != pageSize) {
				sb.append("&pageSize=" + pageSize);
			}
			sb.append("\"><li>&lt;上一页</li></a>");
		}
		int startPage = 1;
		int endPage = 1;
		int cycle = 9;
		int middlePage = cycle / 2;
		if (middlePage != 0) {
			startPage = currentPage - middlePage;
			if (startPage < 1) {
				startPage = 1;
			}
		}

		endPage = startPage + cycle - 1;

		int totalPage = (this.totalCount + this.pageSize - 1) / this.pageSize;
		endPage = endPage >= totalPage ? totalPage : endPage;

		for (; startPage <= endPage; startPage++) {
			if (currentPage != startPage) {
				if (StringUtils.isNoneBlank(condition)) {
					sb.append("<a href=\"" + uri + "?" + condition + "&currentPage=" + startPage);
				} else {
					sb.append("<a href=\"" + uri + "?currentPage=" + startPage);
				}
				if (null != pageSize && 0 != pageSize) {
					sb.append("&pageSize=" + pageSize);
				}
				sb.append("\"><li>" + startPage + "</li></a>");
				continue;
			} else {
				sb.append("<li>" + startPage + "</li>");
			}
		}
		if (currentPage < endPage) {
			if (StringUtils.isNoneBlank(condition)) {
				sb.append("<a href=\"" + uri + "?" + condition + "&currentPage=" + (currentPage + 1));
			} else {
				sb.append("<a href=\"" + uri + "?currentPage=" + (currentPage + 1));
			}
			if (null != pageSize && 0 != pageSize) {
				sb.append("&pageSize=" + pageSize);
			}
			sb.append("\"><li>下一页&gt;</li></a>");
		}

		sb.append("<li class=\"page_spec\">");
		sb.append("共" + pageInfo.getTotalPage() + "页");
		sb.append(" 到第<input type=\"text\" id=\"tx_currentPage\" class=\"text_spec\" value=\"" + currentPage + "\" />页</li>");
		sb.append("<li class=\"page_spec\"><button type=\"button\" id=\"btn_jump\" onclick=\"jumpToPage();\" class=\"btn\">确定</button></li></div>");

		sb.append("<script charset=\"utf-8\" type=\"text/javascript\">");
		sb.append("function jumpToPage(){");

		sb.append("window.location.href=\"" + uri);
		StringBuffer jumpUrl = new StringBuffer();
		if (StringUtils.isNotBlank(condition)) {
			jumpUrl.append("?" + condition);
		}
		if (jumpUrl.length() == 0) {
			jumpUrl.append("?");
		} else {
			jumpUrl.append("&");
		}
		jumpUrl.append("currentPage=\"+" + "document.getElementById('tx_currentPage').value+\"");

		if (null != pageSize && pageSize != 0) {
			jumpUrl.append("&pageSize=" + pageSize);
		}
		sb.append(jumpUrl + "\";");
		sb.append("}");
		sb.append("</script>");

	}

	/**
	 * 拼写查询条件，并将查询条件放入request.attribute中,如果传入参数为集合，则attribute中的值也为集合
	 * 
	 * @param req
	 * @return
	 */
	private static String getCondition(HttpServletRequest req) {
		StringBuffer sb = new StringBuffer();
		Enumeration<String> names = req.getParameterNames();
		while (names.hasMoreElements()) {
			String name = names.nextElement();
			if (name.equals("pageSize") || name.equals("currentPage")) {
				continue;
			}
			String[] values = req.getParameterValues(name);
			if (null != values && values.length > 1) {
				List<String> attrs = new ArrayList<String>();
				for (int i = 0; i < values.length; i++) {
					String temp = values[i];
					temp = null == temp || "null".equals(temp.trim()) || "".equals(temp.trim()) ? null : temp.trim();

					sb.append(name + "=" + temp + "&");
					attrs.add(temp);
				}
				req.setAttribute(name, attrs);
			} else if (null != values && values.length == 1) {
				sb.append(name + "=" + values[0] + "&");
				req.setAttribute(name, values[0]);
			}
		}
		if (sb.length() > 0) {
			return sb.toString().substring(0, sb.length() - 1);
		} else {
			return "";
		}
	}

	@Override
	public int doEndTag() throws JspException {
		release();
		return super.doEndTag();
	}

	@Override
	public void release() {
		super.release();
		requestUrl = null;
		currentPage = null;
		divClass = null;
		requestUrl = null;
		pageSize = null;
		totalCount = null;
	}

	public void setRequestUrl(String requestUrl) {
		this.requestUrl = requestUrl;
	}

	public void setCurrentPage(Integer currentPage) {
		this.currentPage = currentPage;
	}

	public void setDivClass(String divClass) {
		this.divClass = divClass;
	}

	public void setPageSize(Integer pageSize) {
		this.pageSize = pageSize;
	}

	public void setTotalCount(Integer totalCount) {
		this.totalCount = totalCount;
	}
}
